#include "stdafx.h"

class K
{
	//static void f() const{}//static: class, const : object
	//static virtual void h(){}//as above
	//virtual static void g(){}//as above
};

class A
{

};

class B
{
	B(){}
	~B(){}
};

class C
{
	C(){}
	virtual ~C(){}
};

TEST(obj, sizeof)
{
	EXPECT_EQ(1, sizeof(A));
	EXPECT_EQ(sizeof(A), sizeof(B));
	char* p = NULL;
	EXPECT_EQ(4, sizeof(p));
	EXPECT_EQ(sizeof(p), sizeof(C));
}


class D
{
public:
	int v;
	int k;
	D(int v_)
		:v(v_)
	{
	}
	int p1()
	{
		return 1;
	}
	int p2()
	{
		return v;
	}
	int p3()
	{
		//this;//nothing;
		//this->v;//also nothing
		this->v = 3;//death
		return 1;
	}
};

TEST(obj, null)
{
	D* dp = NULL;
	ASSERT_EQ(1, dp->p1());
	EXPECT_DEATH(dp->p2(), "");
	EXPECT_DEATH(dp->p3(), "");

	EXPECT_EQ(sizeof(int), (int) &(dp->k));
}

TEST(ref, null)
{
	int* ip = NULL;
	EXPECT_EQ(NULL, ip);
	int& ir = *ip;
	EXPECT_EQ(NULL, &ir);
}

class E
{
public:
	virtual ~E()
	{}
	virtual int f()
	{
		return 1;
	}
};

class F
	:public E
{
public:
	int f()
	{
		return 2;
	}
};

int e1(E e)
{
	return e.f();
}
int e2(E& e)
{
	return e.f();
}
int e3(E* e)
{
	return e->f();
}

TEST(polymorphic, param)
{
	F f;
	EXPECT_EQ(1, e1(f));
	EXPECT_EQ(2, e2(f));
	EXPECT_EQ(2, e3(&f));
}
void szf(char str[100])
{
	EXPECT_EQ(4, sizeof(str));
	EXPECT_EQ(20, strlen(str));
}
TEST(sizeof, a)
{
	char str[] = "http://www.xxxxx.com";
	EXPECT_EQ(21, sizeof(str));
	szf(str);
	int k[] = {1,2,3,4};
	EXPECT_EQ(1, *k);
	EXPECT_EQ(2, *(k + 1));

	char* p = new char[5];
	delete [] p;
	strcpy(p, "hello");
	cout<<p<<endl;
}


TEST(sizeof, b)
{
	struct k
	{
		double a;
		char b;
		int c;
	};

	EXPECT_EQ(24, sizeof(k));
}
TEST(daisy, gb)
{
	//daisy = 2;
	int $d = 23;
	int $$ = 33;
	cout<<$d<<endl;
	cout<<$$<<endl;
	int a = 5;
	int b = 3;
	int c = a^b<<2;
	EXPECT_EQ(a^(b<<2), c);
}

TEST(daisy, two_dim)
{
	int arr[2][3] = {{1,2,3},{4, 5, 6}};

	EXPECT_EQ(arr, &arr[0]);
	EXPECT_EQ(*arr, &arr[0][0]);
	EXPECT_EQ(arr + 1, &arr[1]);
	EXPECT_EQ(**arr, arr[0][0]);
	

	EXPECT_EQ(*arr, &arr[0][0]);
	EXPECT_EQ(*(arr) + 1, &arr[0][1]);
	EXPECT_EQ(*(arr + 1) + 1, &arr[1][1]);
	EXPECT_EQ(*(*(arr) + 2), arr[0][2]);
}

class Bc
{
public:
	virtual void f()
	{
		cout<<"Bc"<<endl;
	}
	void g()
	{
		cout<<"Bc g"<<endl;
	}
};
class Dr1
	:virtual public Bc
{
public:
	virtual void f()
	{
		cout<<"Dr1"<<endl;
	}
};

class Dr2
	:virtual public Bc
{
public:
	//virtual void f()
	//{
	//	cout<<"dr2"<<endl;
	//}
};

class Drr
	:public Dr1, public Dr2
{
public:
};

TEST(vir, inherit)
{
	Drr drr;
	drr.f();
	drr.g();
}

class X1
{
public:
	int f()
	{
		return 1;
	}
private:
	virtual int k()
	{
		return 1;
	}
friend class X3;
};

class X2
	:public X1
{
public:
	int f()
	{
		return 2;
	}
//public:
private:
	int k()
	{
		//X1::k();
		return 2;
	}
};
class X3
{
public:
	X3()
	{
		X1* x1 = new X2();
		EXPECT_EQ(2, x1->k());
	}
};
class X4
{
public:
	virtual void f() = 0;
};
class X5
{
public:
	virtual void g() = 0;
};
class X6:
	public X4, public X5
{
	void f()
	{
		cout<<"f"<<endl;
	}
	void g()
	{
		cout<<"g"<<endl;
	}
};
TEST(odd, cover)
{
	X1* x1 = new X2();
	EXPECT_EQ(1, x1->f());
	delete x1;
	X3 x3;
	X4* x4 = new X6();
	x4->f();
	delete x4;
	X5* x5 = new X6();
	x5->g();
	delete x5;
}

TEST(chptr, xx)
{
	char *a = "123456";

	const char* p1 = a;
	char const *p2 = a;
	char* const p3 = a;
	const char* const p4 = a;

	//*p1 = 'v';
	//*p2 = a;
	//p3 = a;
	//p4 = a;
	//*p4 = 's';
}